//  
//    String+StringHeight.swift
//    Swift-Extension
//  
//    Created by tianXin on 2017/7/21.
//    Copyright © 2017年 田鑫. All rights reserved.
//  

import Foundation
import UIKit

extension String {
    
    //  Fixed width of the text is true height
    func getSize(_ fontSize: CGFloat,width: CGFloat = CGFloat(MAXFLOAT)) -> CGSize {
        
        let font = UIFont.systemFont(ofSize: fontSize)
        let constraint = CGSize(width: width, height: font.lineHeight)
        
        if IOSVERSION >= 7.0 {
            
            let dict = [NSFontAttributeName: font]
            let size = self.boundingRect(with: constraint, options: .usesLineFragmentOrigin, attributes: dict, context: nil).size
            
            return size
        }
        
        return .zero
    }
    
    //  Text style
    static func getSize(_ text: String, color: UIColor, font: UIFont, width: CGFloat, lineSpacing: CGFloat, alignment: NSTextAlignment = .left) -> [String:Any]? {
        
        let paraStyle = NSMutableParagraphStyle()
        paraStyle.alignment = alignment
        paraStyle.lineBreakMode = .byCharWrapping
        let attrDict = [NSParagraphStyleAttributeName:paraStyle,NSFontAttributeName:font,NSForegroundColorAttributeName:color]
        let attributedStr = NSAttributedString(string: text, attributes: attrDict);
        let option: NSStringDrawingOptions = [.usesLineFragmentOrigin, .usesFontLeading]
        let constraint = CGSize(width: width, height: CGFloat.greatestFiniteMagnitude)
        let frame = attributedStr.boundingRect(with: constraint, options: option, context: nil)
        let size = CGSize(width: CGFloat(ceilf(Float(frame.width))), height: CGFloat(ceilf(Float(frame.height))))
        
        return ["kAttributedText": attributedStr,"kSize": size]
    }
    /**
     Get the height with the string.
     
     - parameter attributes: The string attributes.
     - parameter fixedWidth: The fixed width.
     
     - returns: The height.
     */
    func heightWithStringAttributes(_ attributes: [String: AnyObject], fixedWidth: CGFloat) -> CGFloat {
        
        guard self.characters.count > 0 && fixedWidth > 0 else {
            
            return 0
        }
        
        let size = CGSize(width: fixedWidth, height: CGFloat.greatestFiniteMagnitude)
        let text = self as NSString
        let rect = text.boundingRect(with: size, options: .usesLineFragmentOrigin, attributes: attributes, context:nil)
        
        return rect.size.height
    }
    /**
     Get the height with font.
     
     - parameter font:       The font.
     - parameter fixedWidth: The fixed width.
     - returns: The height.
     */
    func heightWithFont(_ font: UIFont = .systemFont(ofSize: 18), fixedWidth: CGFloat) -> CGFloat {
        
        guard self.characters.count > 0 && fixedWidth > 0 else {
            
            return 0
        }
        
        let size = CGSize(width: fixedWidth, height: .greatestFiniteMagnitude)
        let text = self as NSString
        let rect = text.boundingRect(with: size, options: .usesLineFragmentOrigin, attributes: [NSFontAttributeName : font], context:nil)
        
        return rect.size.height
    }
    
    /**
     Get the height with font.
     
     - parameter font:       The font.
     - parameter fixedWidth: The fixed width.
     
     - returns: The height.
     */
    static func HeightWithFont(_ font : UIFont = .systemFont(ofSize: 18)) -> CGFloat {
        
        let string = "One"
        let size   = CGSize(width: 200, height: CGFloat.greatestFiniteMagnitude)
        let text   = string as NSString
        let rect   = text.boundingRect(with: size, options: .usesLineFragmentOrigin, attributes: [NSFontAttributeName: font], context:nil)
        
        return rect.size.height
    }
    /**
     Get the width with the string.
     
     - parameter attributes: The string attributes.
     
     - returns: The width.
     */
    func widthWithStringAttributes(_ attributes: [String: AnyObject]) -> CGFloat {
        
        guard self.characters.count > 0 else {
            
            return 0
        }
        
        let size = CGSize(width: CGFloat.greatestFiniteMagnitude, height: 0)
        let text = self as NSString
        let rect = text.boundingRect(with: size, options: .usesLineFragmentOrigin, attributes: attributes, context:nil)
        
        return rect.size.width
    }
    
    /**
     Get the width with the string.
     
     - parameter font: The font.
     
     - returns: The string's width.
     */
    func widthWithFont(_ font : UIFont = .systemFont(ofSize: 18)) -> CGFloat {
        
        guard self.characters.count > 0 else {

            return 0
        }
        
        let size = CGSize(width: CGFloat.greatestFiniteMagnitude, height: 0)
        let text = self as NSString
        let rect = text.boundingRect(with: size, options: .usesLineFragmentOrigin, attributes: [NSFontAttributeName: font], context:nil)
        
        return rect.size.width
    }
}
